<template>
  <div ref="contentRef" class="markdown-content" @click="handleClick"></div>
</template>

<script setup>
import { message } from 'ant-design-vue'
import hljs from 'highlight.js'
import 'highlight.js/styles/atom-one-dark-reasonable.css'
import MarkdownIt from 'markdown-it'
import { onMounted, ref, watch } from 'vue'

const props = defineProps({
  source: String
})

const contentRef = ref(null)
const codeBlockStates = ref({}) // 控制展开/收起状态
let md

// 生成唯一的 code block ID
const generateCodeId = () => 'code-' + Math.random().toString(36).substr(2, 9)

// 自定义代码块渲染
const renderCodeBlock = (tokens, idx, options, env, self) => {
  const token = tokens[idx]
  const language = token.info.trim().split(/\s+/g)[0] || ''
  const rawCode = token.content
  const codeId = generateCodeId()

  // 是否有该语言的高亮支持
  const langName = hljs.getLanguage(language) ? language : 'plaintext'

  const highlightedCode = hljs.highlight(rawCode, {
    language: langName
  }).value

  // 初始状态：默认展开（也可以改为超过10行才收起）
  const lines = rawCode.split('\n').length
  const shouldCollapse = lines > 10
  const isExpanded = !shouldCollapse || (codeBlockStates.value[codeId] ?? true)

  const toggleIcon = isExpanded ? '▼' : '▶'
  const displayStyle = isExpanded ? 'block' : 'none'

  // 保存初始状态
  if (shouldCollapse && !(codeId in codeBlockStates.value)) {
    codeBlockStates.value[codeId] = isExpanded
  }

  return `
    <div class="code-container" data-code-id="${codeId}" style="margin: 1em 0; border-radius: 8px; border: 1px solid #2c3e50; overflow: hidden; font-size: 14px;">
      <div class="code-toolbar" style="background: #222427; color: #fff; padding: 6px 10px; display: flex; justify-content: space-between; align-items: center; font-size: 12px;">
        <span>${language || 'code'}</span>
        <div style="display:flex; align-items: center;">
          <div class="toggle-code" data-code-id="${codeId}" style="margin-right: 10px; cursor: pointer;" title="展开/收起">
           <span class="toggle-icon" style="font-size: 10px;">${toggleIcon}</span>
          </div>
          <div class="copy-code-button" data-code-id="${codeId}" style="cursor: pointer;" title="复制代码">
            <img src="/icon/copy-white.svg" style="width: 16px;"/>
          </div>
        </div>
      </div>
      <pre style="margin: 0; display: ${displayStyle};"><code class="code-item hljs ${langName}">${highlightedCode}</code></pre>
    </div>
  `
}

onMounted(() => {
  md = new MarkdownIt({
    html: false,
    linkify: true,
    typographer: true,
    highlight: function (/*str, lang*/) {
      return ''
    }
  })

  // 替换 fence（代码块）渲染规则
  md.renderer.rules.fence = renderCodeBlock

  renderContent()
})

watch(
  () => props.source,
  () => {
    renderContent()
  }
)

const renderContent = () => {
  if (contentRef.value) {
    contentRef.value.innerHTML = md.render(props.source || '')
  }
}

// 点击事件处理
const handleClick = (e) => {
  // 复制按钮
  if (e.target.classList.contains('copy-code-button') || e.target.closest('.copy-code-button')) {
    const button = e.target.closest('.copy-code-button')
    const codeId = button.dataset.codeId
    const codeEl = contentRef.value.querySelector(
      `.code-container[data-code-id="${codeId}"] .code-item`
    )
    const text = codeEl?.textContent || ''
    navigator.clipboard.writeText(text).then(() => {
      message.success('复制成功')
      button.innerHTML = '<img src="/icon/yes.svg" style="width: 14px;"/>'
      setTimeout(() => {
        button.innerHTML = '<img src="/icon/copy-white.svg" style="width: 16px;"/>'
      }, 2000)
    })
    return
  }

  // 展开/收起按钮
  if (e.target.classList.contains('toggle-code') || e.target.closest('.toggle-code')) {
    const button = e.target.closest('.toggle-code')
    const codeId = button.dataset.codeId
    const codeContainer = contentRef.value.querySelector(
      `.code-container[data-code-id="${codeId}"]`
    )
    const pre = codeContainer?.querySelector('pre')
    const icon = button.querySelector('.toggle-icon') || button

    const isExpanded = codeBlockStates.value[codeId]
    const newStatus = !isExpanded
    codeBlockStates.value[codeId] = newStatus

    pre.style.display = newStatus ? 'block' : 'none'
    icon.textContent = newStatus ? '▼' : '▶'
  }
}
</script>

<style>
.markdown-content img {
  max-width: 100%;
  height: auto;
}
.markdown-content pre {
  margin: 0;
  border-radius: 0;
  font-size: 14px;
}
.markdown-content code {
  font-family: 'Courier New', monospace;
}
</style>
